package com.wn.main.ui.system.view

import android.os.Bundle
import androidx.core.view.isVisible
import androidx.fragment.app.viewModels
import androidx.lifecycle.Lifecycle
import androidx.lifecycle.lifecycleScope
import androidx.lifecycle.repeatOnLifecycle
import androidx.recyclerview.widget.LinearLayoutManager
import com.blankj.utilcode.util.ConvertUtils
import com.blankj.utilcode.util.ToastUtils
import com.scwang.smart.refresh.layout.api.RefreshLayout
import com.scwang.smart.refresh.layout.listener.OnRefreshLoadMoreListener
import com.wn.common.constant.KEY_ID
import com.wn.common.model.ArticleList
import com.wn.common.provider.LoginServiceProvider
import com.wn.common.provider.UserServiceProvider
import com.wn.framework.base.BaseFragment
import com.wn.framework.decoration.NormalItemDecoration
import com.wn.main.R
import com.wn.main.databinding.FragmentArticleListBinding
import com.wn.main.ui.system.adapter.SystemArticleAdapter
import com.wn.main.ui.system.viewmodel.ArticleListViewModel
import com.wn.network.error.ERROR
import dagger.hilt.android.AndroidEntryPoint
import kotlinx.coroutines.Job
import kotlinx.coroutines.flow.collect
import kotlinx.coroutines.launch
import javax.inject.Inject

/**
 * @Author: wn
 * @Date: 2025/6/3 16:51
 * @Description: 体系中 viewpager2 对应的 Fragment -- 数据列表
 */
@AndroidEntryPoint
class ArticleListFragment : BaseFragment<FragmentArticleListBinding>(), OnRefreshLoadMoreListener {

  override fun getLayoutRes() = R.layout.fragment_article_list

  private val viewModel by viewModels<ArticleListViewModel>()

  @Inject
  lateinit var mAdapter: SystemArticleAdapter

  @Inject
  lateinit var normalItemDecoration: NormalItemDecoration

  // 页码
  private var mPage = 1

  // 调用 API 所需的 id
  private var mId = 0

  override fun initView() {
    mBinding.apply {
      refreshLayout.apply {
        autoRefresh()
        setOnRefreshListener(this@ArticleListFragment)
        setOnLoadMoreListener(this@ArticleListFragment)
      }

      recyclerView.apply {
        layoutManager = LinearLayoutManager(requireContext())
        adapter = mAdapter
        addItemDecoration(normalItemDecoration.apply {
          setLastBottom(true)
          setBounds(
            ConvertUtils.dp2px(12.0F),
            ConvertUtils.dp2px(12.0F),
            ConvertUtils.dp2px(12.0F),
            ConvertUtils.dp2px(12.0F)
          )
        })
      }
    }
    // 点击 是否收藏
    mAdapter.onClickCollect = { position, item ->
      /**
       * 登录后 收藏文章
       * 未登录 -- 跳转登录页
       */
      if (UserServiceProvider.isLogin()) {
        collectArticle(position, item)
      } else {
        LoginServiceProvider.toLogin(requireContext())
      }
    }
  }

  override fun initData() {
    mId = arguments?.getInt(KEY_ID) ?: 0
  }

  /**
   * 获取数据列表
   * 刷新 mPage = 1
   * 加载 mPage ++
   */
  private lateinit var job: Job
  private fun getData() {
    if (::job.isInitialized) job.cancel()
    job = lifecycleScope.launch {
      lifecycle.repeatOnLifecycle(Lifecycle.State.STARTED) {
        viewModel.getArticleList(mPage, mId).collect {
          if (mPage == 1) {
            // 加载更多 最后没有数据 得到的就是 null 所里 这里 骨架屏只针对首次刷新 即 mPage == 1
            mBinding.viewEmptyData.isVisible = it?.datas.isNullOrEmpty()
            it ?: return@collect
            mAdapter.setData(it.datas)
            mBinding.refreshLayout.finishRefresh()
          } else {
            mAdapter.addData(it?.datas)
            mBinding.refreshLayout.finishLoadMore()
          }
        }
      }
    }
  }

  override fun onRefresh(refreshLayout: RefreshLayout) {
    mPage = 1
    getData()
  }

  override fun onLoadMore(refreshLayout: RefreshLayout) {
    mPage++
    getData()
  }

  private lateinit var jobCollect: Job

  /**
   * 收藏 or 取消收藏             -- adapter 更新某一个位置上的数据
   * @param position Int        -- 位置
   * @param item ArticleInfo    -- 数据
   */
  private fun collectArticle(position: Int, item: ArticleList.ArticleInfo) {
    if (::jobCollect.isInitialized) jobCollect.cancel()
    jobCollect = lifecycleScope.launch {
      lifecycle.repeatOnLifecycle(Lifecycle.State.STARTED) {
        // 收藏 or 取消收藏
        launch {
          val collect = item.collect ?: false
          viewModel.collectArticle(item.id ?: 0, collect) { code, _ ->
            // 错误码是 未登陆 跳转到登陆页
            if (code == ERROR.UN_LOGIN.code) {
              // 跳转到登陆页
              LoginServiceProvider.toLogin(requireContext())
            }
          }.collect {
            // 这里根据点击之前的 collect 状态来判断是收藏还是取消收藏  -- true 表示要取消 ,false 表示要收藏
            val tipsRes =
              if (collect) com.wn.framework.R.string.collect_cancel else com.wn.framework.R.string.collect_success
            ToastUtils.showShort(tipsRes)
            /**
             * 更改 item 的 collect 状态 取反
             * 更新某一个位置上的数据
             */
            item.collect = !collect
            mAdapter.updateItem(position, item)
          }
        }
        // 加载 loading
        launch {
          viewModel.loading.collect {
            if (it) showLoading() else dismissLoading()
          }
        }
      }
    }
  }

  /**
   * Home键或者锁屏 后 如果不 cancel 返回时数据会重复请求  -- stop
   * viewPager 滑动 -- pause
   */
  override fun onStop() {
    if (::job.isInitialized) job.cancel()
    if (::jobCollect.isInitialized) jobCollect.cancel()
    super.onStop()
  }

  companion object {
    fun newInstance(id: Int): ArticleListFragment = ArticleListFragment().apply {
      arguments = Bundle().apply { putInt(KEY_ID, id) }
    }
  }
}